package com.wskeee.ec.components.tree
{
	import flash.utils.Dictionary;
	
	import com.wskeee.ec.components.list.BaseListData;
	import com.wskeee.ec.components.list.List;
	import com.wskeee.ec.interfaces.IListCellRenderer;
	
	public class Tree extends List
	{
		public function Tree()
		{
			super();
			itemRenderer = TreeDefaultRenderer;
		}
		
		//========================= initialize ==================
		override protected function initialize():void
		{
			super.initialize();
			initDataManager();
		}
		//========================= end =========================
		
		
		//========================= dataManager =================
		protected var treeDataManager:TreeDataManager;
		protected function initDataManager():void
		{
			treeDataManager = new TreeDataManager();
		}
		//========================= end =========================
		
		//========================= validate ====================
		//---------------------
		//commitProperties
		//---------------------
		override protected function commitProperties():void
		{
			super.commitProperties();
			var itemDatas:Array = items as Array;
			if(dataProviderChanged || openItemChanged || showRootChanged)
			{
				itemDatas = treeDataManager.getTreeDataToListData();
				if(!showRoot && itemDatas && itemDatas.length>0)
					itemDatas.shift();
				dataProviderChanged = openItemChanged = showRootChanged = false;
				items = itemDatas;
				reflashVScrollBar();
				if(isNeedReCreateRender())
					invalidateRecreateRender();
				invalidateReflashRender();
			}
		}
		
		//========================= end =========================
		
		//========================= act protected ===============
		override protected function initRenderItem(item:IListCellRenderer):void
		{
			super.initRenderItem(item);
			item.addEventListener(TreeEvent.ITEM_OPEN,onItemOpen);
		}
		protected function onItemOpen(evt:TreeEvent):void
		{
			expendItem(evt.data.listData.data,evt.data.isOpen);
		}
		override protected function destoryRenderItem(item:IListCellRenderer):void
		{
			super.destoryRenderItem(item);
			item.removeEventListener(TreeEvent.ITEM_OPEN,onItemOpen);
		}
		//========================= end =========================
		
		//========================= propertes ===================
		//---------------------
		//dataProvider
		//---------------------
		protected var dataProviderChanged:Boolean = false;
		override public function set dataProvider(value:Object):void
		{
			_dataProvider = value;
			treeDataManager.init(value,this);
			dataProviderChanged = true;
			invalidateProperties();
		}
		//---------------------
		//showRoot
		//---------------------
		private var showRootChanged:Boolean = false;
		private var _showRoot:Boolean = false;
		public function set showRoot(bo:Boolean):void
		{
			_showRoot = bo;
			showRootChanged = true;
			invalidateProperties();
		}
		public function get showRoot():Boolean
		{
			return _showRoot;
		}
		
		//---------------------
		//openNode
		//---------------------
		protected var openItemChanged:Boolean = false;
		/**
		 * 记录已打开的 node  
		 */		
		protected var openItems:Dictionary = new Dictionary();
		//========================= end =========================
		
		
		//========================= act =========================
		/**
		 * 展开 item  
		 * @param item	Object
		 * @param open	true/false
		 *  
		 */
		public function expendItem(item:Object,open:Boolean,dispatchEvent:Boolean = true):void
		{
			var nodeData:TreeListData = item is BaseListData ? item as TreeListData : treeDataManager.getListDataForData(item);
			if(!nodeData || !nodeData.hasChildren)return;
			open ? openItems[item] = true : delete openItems[item];
			
			for(var i:int=0,len:int=nodeData.children.length;i<len;i++)
				expendItem(nodeData.children[i].data,open);
			
			openItemChanged = true;
			invalidateProperties();
		}
		//========================= end =========================
		
		
		//========================= utils =======================
		override protected function getListData(data:Object):BaseListData
		{
			return treeDataManager.getListDataForData(data);
		}
		//========================= end =========================
	}
}